#pragma once

#include <compl.h>


#define RADIX_CONT_NULL (NULL)
/* radix_t 索引 */
typedef void		*radix_t;
typedef word_t		ridx_t;
typedef word_t		rkey_t;

DECL_CEFF(radix_t, val_decoder, (radix_t encoded_val, rkey_t key))
DECL_CEFF(radix_t, val_encoder, (radix_t decoded_val, rkey_t key))
DECL_CEFF(void *, rdx_alloc, (size_t size))
DECL_CEFF_HDL(rdx, val_decoder, val_encoder, rdx_alloc)

DECL_SINTF(radix_t, radix_find, (radix_t *rdx, radix_t **prdx, rkey_t key))
DECL_MINTF(rdx, radix_find)
// typedef struct rdx_chdl{ 
//	 val_decoder_eff_t const *val_decoder; 
//	 val_encoder_eff_t const * val_encoder; 
//	 rdx_alloc_eff_t const * rdx_alloc; 
// }rdx_chdl_t;

// DEF_CEFF_HANDLER(rdx)
/* 多级基数树结构, 根据key编码的值去访问 */

/* 可以实现一级的flatmap, 多级cap表, 页表 */

/* 更好的组合以及管理副作用 */

/* 方案1, 传lvl,递归式 */
/* get_val(key, key_decoder, val_decoder) -> (val_obj | NULL) */
/* set_val(key, val, key_decoder, val_encoder) -> succ|fail */
/* key_decoder(key, lvl, &next_key) -> key | -1(ender) */
/* val_encoder(val, lvl, encode_key) -> encode_val*/
/* val_decoder(encode_val, lvl, encode_key) -> */


/* 方案2, 直接传continue, 这样组合灵活性更高? */
/* radix_find(next, key) */

/* 本质是组合find过程, find最后返回一个指针用于写 */
/* radix_set(next, key, val) -> entry_ptr */

typedef radix_t (radix_find_f)(radix_t *rdx, radix_t **prdx, rkey_t key);

// typedef radix_t *(* rdxv_decoder_f)(radix_t *encoded_val);
// typedef radix_t *(* radix_alloc_f)(size_t size);


/* nil */
SAI radix_t id_radix_find(radix_t *rdx, radix_t **prdx, rkey_t key){
	PARAM_USED(rdx); PARAM_USED(prdx); PARAM_USED(key);
	return (radix_t)rdx;
}

SAI radix_t id_val_decoder(radix_t encoded_val, rkey_t key){
	PARAM_USED(key);
	return encoded_val;
}
SAI radix_t id_val_encoder(radix_t val, rkey_t key){
	PARAM_USED(key);
	return val;
}

SAI void *id_radix_alloc(size_t size){
	PARAM_USED(size);
	return NULL_PTR;
}

SAI radix_t __radix_find_comp(radix_find_f *next, radix_t *rdx, radix_t **prdx, rkey_t key, hword_t const cur_keybit, 
__CEFF__(rdx)){
	radix_t val;
	/* 查询后走下一层 */
	/* 解码失败如何做处理呢 */
	if (!rdx) {
		/* 如果是空，是否尝试建立 */
		rdx = (radix_t *)(hdl->rdx_alloc(BIT(cur_keybit) * sizeof(radix_t)));
		/* if (!rdx) return NULL; */
		ASSUME(rdx); /* WARN: 关键性能路径，假设一定成立，忽略静态分析器 */
		/* 在指定位置填入指针 */
		**prdx = hdl->val_encoder((radix_t)rdx, key);
		/* 这里不进行加密吗？ */
	}
	/* 先解码key获得索引 key->idx */
	word_t idx = key & MASK_LOW(cur_keybit);
	/* 解码获得 */
	*prdx = &rdx[idx];
	val = hdl->val_decoder(**prdx, key);
	/* 返回val */
	/* 解码失败或者解出空值 */
	/* 解码下一部分 */
	return next((radix_t *)val, prdx, key >> cur_keybit);
}



#define DEF_RADIX_FIND_COMP(name, cur_bit, val_decoder, val_encoder, radix_alloc)				\
NEW_CEFF_HDL(rdx, name, val_decoder, val_encoder, radix_alloc)							\
SAI radix_t name##_radix_find_comp(radix_find_f *next, radix_t *rdx, radix_t **prdx, rkey_t key){		\
	return __radix_find_comp(next, rdx, prdx, key, cur_bit, &GET_CEFF_HDL(name));		}		\

#define APPEND_RADIX_FIND_COMP(unlinkedc1, c2) \
SAI radix_t c2##_radix_find(radix_t *rdx, radix_t **prdx, rkey_t key);\
SAI radix_t unlinkedc1##_radix_find(radix_t *rdx, radix_t **prdx, rkey_t key){					\
	return unlinkedc1##_radix_find_comp(c2##_radix_find, rdx, prdx, key);					\
}

/* 第一个是名字
	name - 名字
	... - 需要连接的列表 */
#define DEF_RADIX_FIND(name, ...)	\
MAPL(APPEND_RADIX_FIND_COMP, GEN_PAIRLIST(__VA_ARGS__, id))\
static PARAM_NONULL(1) ALWAYS_INLINE radix_t name##_radix_find(radix_t *rdx, radix_t **prdx, rkey_t key) {	\
	return EXPAND(DEFER(__MCAT) (HD(__VA_ARGS__) ,_radix_find)) (rdx, prdx, key);}				\
MAY_UNUSED NEW_MINTF(rdx, name, name##_radix_find)




/* flat */
/* 查找的过程中需要建立索引结构吗?如果建立失败则返回空 */

/* 页表 */

/* cap表 */

